package com.onpositive.units;

import java.util.Collection;
import java.util.Collections;
import java.util.LinkedHashMap;
import java.util.Map;

import org.w3c.dom.Element;
import org.w3c.dom.Node;
import org.w3c.dom.NodeList;

import com.onpositive.knowledge.model.values.IHasValue;
import com.onpositive.semantic.model.api.meta.BaseMeta;
import com.onpositive.semantic.model.api.meta.IMeta;

public class TextContent extends ParsedValue {
	
	/**
	 * 
	 */
	private static final long serialVersionUID = -8884191188487129470L;
	public final static String ID = "text-content" ;
	public static final String SECTION_SEPARATOR = "<<< section separator >>>" ;
	
	private LinkedHashMap<String,ParsedSection> storage = new LinkedHashMap<String, ParsedSection>() ;
	
	public TextContent(String comment){ super(comment);}
	
	
	public TextContent( String content, String comment )
	{
		super(comment) ;
		String[] sections = content.split( SECTION_SEPARATOR ) ;
		for( String fullSectionContent : sections )
		{
			ParsedSection pSec = new ParsedSection( fullSectionContent, this, comment ) ;
			this.putSection(pSec) ;
		}		
	}

	public TextContent( ParsedValue pv, String comment )
	{
		super( comment ) ;		
		TextContent other = (TextContent) pv ;
		this.storage = new LinkedHashMap<String, ParsedSection>() ;
		for( Map.Entry<String, ParsedSection> entry : other.storage.entrySet() )
		{			
			String name = entry.getKey() ;
			ParsedSection ps = entry.getValue() ;
			this.storage.put(name,  new ParsedSection(ps,null,this) ) ;
		}
	}
	
	public TextContent( Element element )
	{
		super( element ) ;
		NodeList children = element.getChildNodes() ;
		int l = children.getLength() ;
		for( int i = 0 ; i < l ; i++  )
		{
			Node n = children.item(i) ;
			if( n instanceof Element )
			{
				Element sectionElement = (Element)n ;
				ParsedSection sec = new ParsedSection( sectionElement, this ) ;
				this.putSection( sec ) ;
			}			
		}
	}
	
	private TextContent( TextContent other, LinkedHashMap<String, ParsedSection> value, String comment )
	{
		super( comment ) ;
		this.storage = new LinkedHashMap<String, ParsedSection>() ;
		for( Map.Entry<String, ParsedSection> entry : value.entrySet() )
		{			
			String name = entry.getKey() ;
			ParsedSection ps = entry.getValue() ;
			this.storage.put(name,  new ParsedSection(ps,null,this) ) ;
		}
	}
	
	public void putSection( ParsedSection ps )
	{
//		String name = ps.getName();
//		System.out.print(name + "\n") ;
//		ParsedSection tmp = storage.get( ps.getName() );
//		System.out.print( tmp != null ? tmp.getName() : "null" + "\n\n") ;
		storage.put( ps.getName(), ps ) ;
		
	}
	
	public ParsedSection getSection( String name )
	{
		return name != null ? storage.get(name) : null ;
	}
	@Override
	public void writeValue(Element element)
	{
		super.writeValuePartial(element) ;
		
		for( ParsedSection ps: storage.values()  )
		{
			Element child = element.getOwnerDocument().createElement("value");
			element.appendChild(child) ;
			ps.writeValue(child);
		}
	}
	
	@Override
	public Object value() {
		
		return storage.values() ;
	}
	
	public Collection<ParsedSection> getSections() {
		
		return storage.values() ;
	}

	@Override
	public void setValue(Object obj) {
		// TODO Auto-generated method stub
		
	}

	@Override
	public Object describer() {
		// TODO Auto-generated method stub
		return null;
	}

	@Override
	public String getId() {

		return ID;
	}

	@Override
	public String getValueAsString() {
		// TODO Auto-generated method stub
		return null;
	}
		
	@Override
	public String toString()
	{
		Collection<ParsedSection> values = storage.values();
		if( values == null || values.size() == 0 )
			return "" ;
		
		StringBuilder builder = new StringBuilder() ;
		
		for( ParsedSection ps : values ){
			builder.append( ps.getName() );
			builder.append( "; " );
		}
		return builder.substring( 0, builder.length()-2 ) ;
	}

	@Override
	public int hashCode() {
		final int prime = 31;
		int result = 1;
		result = prime * result + ((ID == null) ? 0 : ID.hashCode());
		result = prime * result + ((storage == null) ? 0 : storage.hashCode());
		return result;
	}

	@Override
	public boolean equals(Object obj)
	{
		if (this == obj)
			return true;
		if (obj == null)
			return false;
		if (getClass() != obj.getClass())
			return false;
		TextContent other = (TextContent) obj;
		if (ID == null) {
			if (other.ID != null)
				return false;
		} else if (!ID.equals(other.ID))
			return false;
		if (storage == null) {
			if (other.storage != null)
				return false;
		} else if (!storage.equals(other.storage))
			return false;
		return true;
	}


	@Override
	public IHasValue clone(Object value, String comment) {
		if( !( value instanceof LinkedHashMap<?,?> ) )
			return null;
		if( comment == null )
			comment = this.getComment() ;
		return new TextContent(this, (LinkedHashMap<String, ParsedSection>) value, comment) ;
	}


	@Override
	public <T> Collection<T> getValues(Class<T> vs) {
		return Collections.emptySet();
	}

	
	
	
	

}
